import Decimal from 'decimal.js';
import Cookies from 'js-cookie';
import QRcode from 'qrcode';
import http from './axios';
import store from '../store';
import { EosModel } from './eos';
import appName from './environments';

let self = null;
/* 国内手机格式 */
export function validateMobile(str) {
  const reg = /^1\d{10}$/;
  return reg.test(str);
}
/* 国际手机格式 */
export function validateMobileGj(str) {
  const reg = /^\d{8,}$/;
  return reg.test(str);
}

/* 邮箱验证 */
export function validateEmail(str) {
  const reg = /^[a-zA-Z0-9_-]+@[a-zA-Z0-9_-]+(\.[a-zA-Z0-9_-]+)+$/;
  return reg.test(str);
}

/* 注册密码验证 字母加数字 >=6, <=18 */
export function validateRegirstPassword(str) {
  const reg = /^(?=.*[a-zA-Z])(?=.*\d)[a-zA-Z\d]{6,18}$/;
  return reg.test(str);
}

/* 钱包密码验证 小写字母+大写字母+数字 >=8, <= 16 */
export function validateRegirstPassword8(str) {
  const reg =/^(?:(?=.*[A-Z])(?=.*[a-z])(?=.*[0-9])).{8,}$|^(?:(?=.*[A-Z])(?=.*[a-z])(?=.*[#@!~%^&*])).{8,}$|^(?:(?=.*[A-Z])(?=.*[0-9])(?=.*[#@!~%^&*])).{8,}$|^(?:(?=.*[a-z])(?=.*[0-9])(?=.*[#@!~%^&*])).{8,}$/; // eslint-disable-line
  return reg.test(str);
}

/* EOS 账户名判断正则 小写字母+数字（1~5之间），且长度必须为12位 */
export function validateEosName(str) {
  const reg = /^.*[a-z]+.*$/;
  const reg2 = /^.*[1-5]+.*$/;
  return reg.test(str) && reg2.test(str) && str.length === 12;
}

/* TRON 账户名需8-32位，只能包含 a-z 0-9 A-Z。 */
export function validateTronName(str) {
  const reg = /^[A-Za-z0-9]{8,32}$/;
  return reg.test(str)
}

/* ETH地址的校验规则
  1、判断地址非空和是否0x开头
  2、把16进制字符串转成10进制数，看是否能否转换成功
  3、判断是否长度是40位（去掉0x）
*/
export function validateETH(str) {
  const reg = /^0x[a-f0-9]{40}$/i;
  return reg.test(str)
}

/* BTC地址的校验规则
  1、3开头的比特币地址，长度为34位。
  2、1开头的比特币地址，长度为26位到34位否转换成功
*/
export function validateBTC(str) {
  // eslint-disable-next-line no-useless-escape
  const reg = /^(1[a-z1-9]{25,33}|3[a-z1-9]{33})$/i;
  return reg.test(str)
}

/* TRON地址的校验规则
*/
export function validateTRON(str) {
  // eslint-disable-next-line no-useless-escape
  const reg = /^T[a-z0-9]{33}$/i;
  return reg.test(str)
}

// 保留两位小数并且整数部分三位一个逗号分隔符的数字金钱标准表示法：
// 这里假设我们即不知道输入数字的整数位数，也不知道小数位数
/* 将100000转为100,000.00形式 */
export function moneyFormat(fmoney) {
  let money = fmoney;
  if (money && money !== null) {
    money = String(money);
    const left = money.split('.')[0];
    let right = money.split('.')[1];
    right = right ? (right.length >= 2 ? `.${right.substr(0, 2)}` : `.${right}0`) : '.00'; // eslint-disable-line
    const temp = left.split('').reverse().join('').match(/(\d{1,3})/g);
    return (Number(money) < 0 ? '_' : '') + temp.join(',').split('').reverse().join('') + right;
  } else if (money === 0) {
    return '0.00';
  }
  return '';
}

// 返回小数位后几位 截取
// number 数值
// p 位数
export function toFixed(number, pp) {
  const num = isNaN(number) || !number ? 0 : number;
  const p = isNaN(pp) || !pp ? 0 : pp;
  // const x = Math.pow(10, p); // eslint-disable-line
  // return (Math.floor(Number(number) * x) / x).toFixed(p);
  var n = (num + '').split('.'); // eslint-disable-line
  var x = n.length > 1 ? n[1] : ''; // eslint-disable-line
  if (x.length > p) { // eslint-disable-line
    x = x.substr(0, p); // eslint-disable-line
  } else { // eslint-disable-line
    x += Array(p - x.length + 1).join('0'); // eslint-disable-line
  } // eslint-disable-line
  return n[0] + (x == '' ? '' : '.' + x); // eslint-disable-line
}

// 处理数据 - 0舍1入 - 针对卖盘
// price 数值
// deep 位数
export function toFixedReset(price, deep) {
  const sellPrice = toFixed(price, deep);
  // 深度合并到个位及小数时
  // 处理前 === 处理后 ？ 是：不进行上合并 | 否：进行上合并
  if (Number(price) === Number(sellPrice) && deep >= 0) {
    return sellPrice;
  }
  // 深度合并到十位及以上
  const min = Decimal(`1e${-deep}`); // 上合并
  if (deep < 0) {
    const t1 = price % min;
    let t = toFixed(price / min, 0);
    if (t1 === 0) {
      return toFixed(min * t, deep);
    }
    t = Number(t) + 1;
    return toFixed(min * t, deep);
  }
  let ipSellPrice = Decimal.add(min, sellPrice).toString();
  ipSellPrice = toFixed(Number(ipSellPrice), deep);
  return ipSellPrice;
}
// 处理数据 - 0舍1入 - 针对买盘
// price 价格
// deep 深度
export function toFixedDown(price, deep) {
  const sellPrice = toFixed(price, deep);
  // 深度合并到个位及小数时
  if (deep >= 0) {
    return sellPrice;
  }
  // 深度合并到十位及以上
  const min = Decimal(`1e${-deep}`); // 下合并
  const t = toFixed(price / min, 0);
  return toFixed(min * t, deep);
}


/*
 ** 加法函数，用来得到精确的加法结果
 ** 返回值：arg1 + arg2的精确结果 Number 型
*/
export function accAdd(arg1, arg2) {
  const num = Decimal(arg1).add(new Decimal(arg2));
  // const m = num.toExponential().match(/\d(?:\.(\d*))?e([+-]\d+)/); // eslint-disable-line
  // const kx = num.toFixed(Math.max(0, (m[1] || '').length - m[2]));
  return num.toFixed();
}

/*
 ** 减法函数，用来得到精确的减法结果
 ** 返回值：arg1 - arg2的精确结果 Number 型
*/
export function accSub(arg1, arg2) {
  const num = new Decimal(arg1).sub(new Decimal(arg2));
  // const m = num.toExponential().match(/\d(?:\.(\d*))?e([+-]\d+)/); // eslint-disable-line
  // const kx = num.toFixed(Math.max(0, (m[1] || '').length - m[2]));
  return num.toFixed();
}

/*
 ** 乘法函数，用来得到精确的乘法结果
 ** 返回值：arg1 * arg2的精确结果 Number 型
*/
export function accMul(arg1, arg2) {
  if (!arg1 || !arg2) {
    return 0
  }
  const num = new Decimal(arg1).mul(new Decimal(arg2));
  // const m = num.toExponential().match(/\d(?:\.(\d*))?e([+-]\d+)/); // eslint-disable-line
  // const kx = num.toFixed(Math.max(0, (m[1] || '').length - m[2]));
  return num.toFixed();
}

/*
 ** 除法函数，用来得到精确的除法结果
 ** 返回值：arg1 / arg2的精确结果 Number 型
*/
export function accDiv(arg1, arg2) {
  if (!arg1 || !arg2) {
    return 0
  }
  const num = new Decimal(arg1).div(new Decimal(arg2));
  // const m = num.toExponential().match(/\d(?:\.(\d*))?e([+-]\d+)/); // eslint-disable-line
  // const kx = num.toFixed(Math.max(0, (m[1] || '').length - m[2]));
  return num.toFixed();
}

// 将科学计数法转换为小数
export function toNonExponential(num) {
  if (num === null) {
    return 0;
  }
  if (isNaN(num)) {
    return 0;
  }
  const fnum = new Decimal(num);
  return fnum.toFixed();
}

/*
 ** 限制输入小数位位数
 ** @params Number value // 输入的数值
 ** @params Number p // 限制输入位数
*/
export function limitNumber(value, p, callback) {
  const str = value ? value.toString() : '';
  if (str.indexOf('.') > 0 && str.split('.')[1].length > 4) {
    setTimeout(() => {
      let back = str.match(/^\d*(\.?\d{0,4})/g)[0];
      if (p === 1) {
        back = str.match(/^\d*(\.?\d{0,1})/g)[0];
      }
      if (p === 2) {
        back = str.match(/^\d*(\.?\d{0,2})/g)[0];
      }
      if (p === 3) {
        back = str.match(/^\d*(\.?\d{0,3})/g)[0];
      }
      // return Number(back);
      callback(back)
    }, 300);
  }
  return value;
}

/* 身份证 */
export function validateIdcard(str) {
  const reg = /(^\d{15}$)|(^\d{18}$)|(^\d{17}(\d|X|x)$)/;
  return reg.test(str);
}

/* 文件格式 */
export function validateFile(str) {
  const list = {
    jpg: 'image',
    png: 'image',
    jpeg: 'image',
    bmp: 'image',
    gif: 'image',
    tif: 'image',
    doc: 'word',
    docx: 'word',
    xls: 'excel',
    xlsx: 'excel',
    pdf: 'pdf',
    txt: 'txt',
    zip: 'zip',
    rar: 'zip',
    '7z': 'zip',
  };
  return list[str.toLowerCase()] || 'other';
}

/* 过滤提交条件 */
export function filterSubmitCondition(item) {
  // 省市区过滤
  if (item.name.indexOf('province') > -1 ||
      item.name.indexOf('city') > -1 ||
      item.name.indexOf('county') > -1 ||
      ((item.input_type === -1 || item.input_type === 4) && !item.option.length)) {
    return String(item.value);
  }
  // 时间戳过滤
  if (item.input_type === 2) {
    if (typeof item.value === 'number') {
      return item.value;
    }
    return Date.parse(item.value) / 1000 || '';
  }
  return item.value;
}

/* Json To Url */
export function JsonToUrl(json) {
  return Object.keys(json).map(key =>
    `${encodeURIComponent(key)}=${encodeURIComponent(json[key])}`
  ).join('&');
}

/**
 * 时间戳转成本地时间
 */
export function toLocalTime(time) {
  const myDate = new Date(time);
  const year = myDate.getFullYear();
  const month = myDate.getMonth() + 1 > 9 ? (myDate.getMonth() + 1) : `0${(myDate.getMonth() + 1)}`;
  const day = myDate.getDate() > 9 ? myDate.getDate() : `0${myDate.getDate()}`;
  const hour = myDate.getHours() > 9 ? myDate.getHours() : `0${myDate.getHours()}`;
  const min = myDate.getMinutes() > 9 ? myDate.getMinutes() : `0${myDate.getMinutes()}`;
  const sec = myDate.getSeconds() > 9 ? myDate.getSeconds() : `0${myDate.getSeconds()}`;

  const str = `${year}-${month}-${day} ${hour}:${min}:${sec}`;
  // const str = `${year}-${month}-${day}`;
  return str;
}

/**
 * 时间戳后台生成(毫秒)
 */
export function getTimestamp(callback) {
  http.get('/common/getTimestamp').then((res) => {
    if (res) {
      callback(res);
    }
  })
}

// 生成uuID
export function getUUID() {
  const s = [];
  const hexDigits = '0123456789abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ';
  for (let i = 0; i < 8; i += 1) {
    s[i] = hexDigits.substr(Math.floor(Math.random() * 62), 1);
  }
  return s.join('');
}

// 解析url参数为数据字典
export function getUrlParams(url) {
  const params = {};
  url.replace(/[?&]+([^=&]+)=([^&]*)/gi, function(str, key, value) { // eslint-disable-line
    params[key] = value;
  });
  return params;
}
// 解析url / 中的最后一个参数
export function getUrlLastName() {
  const s = window.location.pathname;
  const str = s.split('/');
  const file = str.pop();
  const e = file.split('.');
  return e[0];
}

/*
* 多个对象的数组的sort重新排序 调用
* propertyName 排序值
*/
export function createComparison(propertyName) {
  return ((object1, object2) => {
    const value1 = object1[propertyName];
    const value2 = object2[propertyName];
    if (value1 < value2) {
      return -1;
    } else if (value1 > value2) {
      return 1;
    }
    return 0;
  });
}

// 回调父级url
export function handleParentUrl(str) {
  if (!str) return '';
  const params = {
    et: 'https://dice.endless.game/',
    etTest: 'http://dice.endless.game/', // ET test
    eosabc: 'https://eosabc.io/', // 正式
    eosjust: 'https://www.eosjust.com/',
    bloks: 'https://bloks.io/',
    'telos.bloks': 'https://telos.bloks.io/',
    'meetone.bloks': 'https://meetone.bloks.io/',
    'bos.bloks': 'https://bos.bloks.io/',
    newdexTest: 'http://127.0.0.1:8080/',
  }
  return params[str]
}

// 回调父级url
export function countdown(endtime) {
  const t = Date.parse(endtime) - Date.parse(new Date());
  const days = Math.floor(t / (1000 * 60 * 60 * 24));
  let hours = Math.floor((t / (1000 * 60 * 60)) % 24);
  let minutes = Math.floor((t / 1000 / 60) % 60);
  let seconds = Math.floor((t / 1000) % 60);
  hours = hours >= 10 ? hours : `0${hours}`;
  minutes = minutes >= 10 ? minutes : `0${minutes}`;
  seconds = seconds >= 10 ? seconds : `0${seconds}`;
  if (t <= 0) {
    return {
      total: t,
      days: 0,
      hours: '00',
      minutes: '00',
      seconds: '00'
    };
  }
  return { total: t, days, hours, minutes, seconds };
}

// 二维码生成
export function QRcodeCode(QRcodeText, tag, width, callback) {
  // const params = JSON.stringify(this.walletChecked);
  // const canvas = document.getElementById('loginCode');
  const option = {
    width,
    errorCorrectionLevel: 'L'
  };
  QRcode.toCanvas(tag, QRcodeText, option, (err) => {
    callback(err);
  });
}

const EmailHash = {
  'qq.com': 'http://mail.qq.com/',
  'gmail.com': 'http://mail.google.com/',
  'sina.com': 'http://mail.sina.com.cn/',
  '163.com': 'http://mail.163.com/',
  '126.com': 'http://mail.126.com/',
  'yeah.net': 'http://www.yeah.net/',
  'sohu.com': 'http://mail.sohu.com/',
  'tom.com': 'http://mail.tom.com/',
  'sogou.com': 'http://mail.sogou.com/',
  '139.com': 'http://mail.10086.cn/',
  'hotmail.com': 'http://www.hotmail.com',
  'live.com': 'http://login.live.com/',
  'live.cn': 'http://login.live.cn/',
  'live.com.cn': 'http://login.live.com.cn/',
  '189.com': 'http://webmail16.189.cn/webmail/',
  'yahoo.com.cn': 'http://mail.cn.yahoo.com/',
  'yahoo.cn': 'http://mail.cn.yahoo.com/',
  'eyou.com': 'http://www.eyou.com/',
  '21cn.com': 'http://mail.21cn.com/',
  '188.com': 'http://www.188.com/',
  'foxmail.com': 'http://www.foxmail.com/',
  'outlook.com': 'http://www.outlook.com/',
  'aliyun.com': 'https://mail.aliyun.com/'
}

// 获取邮箱链接
export function EmailHost(emailUrl) {
  if (!emailUrl) return null;
  const emailHost = emailUrl.split('@')[1];
  return EmailHash[emailHost] || null;
}

// 获取所有链
export function chainList() {
  const list = [
    {
      value: 'EOS',
      label: 'EOS',
    },
    {
      value: 'BOS',
      label: 'BOS',
    },
    {
      value: 'MEETONE',
      label: 'MEETONE',
    },
    {
      value: 'ENU',
      label: 'ENU',
    },
    {
      value: 'FIBOS',
      label: 'FIBOS',
    },
    {
      value: 'TELOS',
      label: 'TELOS',
    },
    {
      value: 'WAX',
      label: 'WAX',
    },
    {
      value: 'LYNX',
      label: 'LYNX',
    }
  ]
  return list;
}

// 处理不同格式的parseSymbol
export function parseSymbol(val, contract) {
  if (val.toString().indexOf('-') >= 0) {
    return val.split('-');
  }
  if (val.toString().indexOf('_') >= 0) {
    const sy = val.split('_');
    if (sy.length < 3) {
      sy.unshift(contract || '');
    }
    return sy;
  }
  return val;
}

// 处理不同格式的parseSymbol
export function parseCase(val) {
  if (appName === 'eosNewdex') {
    return val.toLowerCase()
  }
  if (appName === 'tronNewdex') {
    return val.toUpperCase()
  }
  return val;
}

// 链的信息跳转生成
export function GetChainHref(chain) {
  const chainArr = {
    eos: 'https://bloks.io',
    bos: 'https://bos.bloks.io',
    // meetone: 'https://meetone.eosx.io',
    meetone: 'https://meetone.bloks.io',
    enu: 'http://enumivo.qsx.io',
    fibos: 'https://explorer.fibos.rocks',
    // telos: 'https://telos.eosx.io',
    telos: 'https://telos.bloks.io',
    wax: 'https://wax.bloks.io',
    lynx: 'https://lynx.bloks.io',
  }
  return chainArr[chain];
}

export function handleVerify(type, result, callback) {
  http.post(`/account/${type}`, result).then((res) => {
    if (res.code !== 0) {
      self.$message.error('Authorization error please try again later');
      localStorage.setItem('Frontend-Token', '');
      callback('error', '服务端验证出错');
      console.log('服务端验证出错'); // eslint-disable-line
      return;
    }
    localStorage.setItem('Frontend-Token', res.token);
    const scat = store.state.app.scatter;
    scat.identity.accounts[0].frontendToken = res.token;
    store.dispatch('setScatter', scat);
    callback('success', result);
  });
}

// 用户授权
export function authorized(t, callback) {
  self = t;
  const token = localStorage.getItem('Frontend-Token');
  if (token) {
    callback('success');
    return;
  }
  const scat = store.state.app.scatter;
  if (scat && !scat.identity) {
    self.$message.error(self.$t('public.signIn'));
    return;
  }
  getTimestamp((timestamp) => {
    EosModel.arbitrarySignature(self, timestamp, (result) => {
      if (result.isError) {
        localStorage.setItem('Frontend-Token', '');
        self.$message.error('Authorization error please try again later');
        callback('error', result.isError);
        console.log('钱包签名问题'); // eslint-disable-line
        return;
      }
      if (appName === 'tronNewdex') {
        handleVerify('verify', result, callback)
        return;
      }
      handleVerify('verifySign', result, callback)
    });
  });
}

// 选择公链
export function choiceChain(chain) {
  if ((chain === 'eos' && appName === 'eosNewdex')
  || (chain === 'tron' && appName === 'tronNewdex')) {
    return;
  }
  const env = process.env.NODE_ENV;
  const hostname = window.location.hostname;
  const protocol = window.location.protocol;
  const hostnames = window.location.hostname.split('.');
  const size = hostnames.length;
  const domain = `${hostnames[size - 2]}.${hostnames[size - 1]}`;
  Cookies.set('tradeCode', chain, { path: '/', domain: `.${domain}`, expires: 30 });
  store.dispatch('setTrade', null);
  const lang = localStorage.getItem('language') || 'en';
  switch (env) {
    case 'tron':
    case 'development':
      if (chain === 'eos' && appName !== 'eosNewdex') {
        location.href = `${protocol}//${hostname}:2000/?language=${lang}`;
      }
      if (chain === 'tron' && appName !== 'tronNewdex') {
        location.href = `${protocol}//${hostname}:2010/?language=${lang}`;
      }
      break;
    default:
      if (chain.toLowerCase() === 'eos') {
        location.href = `https://${domain}/?language=${lang}`;
      } else {
        location.href = `https://${chain}.${domain}/?language=${lang}`;
      }
      break;
  }
}

// 估值单位格式化
export function guzhiForMat(chain) {
  let name = 'EOS';
  switch (chain.toLowerCase()) {
    case 'fibos':
      name = 'FO';
      break;
    case 'lynx':
      name = 'LNX';
      break;
    case 'telos':
      name = 'TLOS'
      break;
    case 'tron':
      name = 'TRX'
      break;
    default:
      name = chain.toUpperCase();
      break;
  }
  return name;
}

// 返回链接
export function getReqUrl(hostname) {
  const env = process.env.NODE_ENV;
  let linkUrl = '';
  switch (env) {
    case 'tron':
    case 'development':
      linkUrl = `http://${process.env.VUE_APP_BASEURL}:${process.env.VUE_APP_PORT1}`
      if (hostname) { // 只需要hostname IP
        linkUrl = process.env.VUE_APP_BASEURL
      }
      break;
    default:
      linkUrl = location.origin;
      break;
  }
  return linkUrl;
}

// 判断是否已经续费会员 - 到期日 <= 360天 ？ 未续费 - 0 ： 已经续费 - 1
export function regIsRenew(vipInfo) {
  const now = new Date().getTime()
  const toLocalDate = toLocalTime(vipInfo.expireTime);
  const expireTime = toLocalDate.replace(/-/g, '/');
  const lastDate = new Date(expireTime).getTime();
  const days = (lastDate - now) / (1000 * 60 * 60 * 24);
  if (days <= 360) {
    return 0;
  }
  return 1
}

export function websizeJump(chain) {
  const env = process.env.NODE_ENV;
  const hostname = window.location.hostname;
  const protocol = window.location.protocol;
  switch (env) {
    case 'tron':
    case 'development':
      window.open(`${protocol}//${hostname}:2020/${chain}`);
      break;
    default:
      // if (hostname.indexOf('vip') >= 0) {
      //   window.open(`https://newpool.vip/${chain}`);
      //   return;
      // }
      // if (hostname.indexOf('io') >= 0) {
      //   window.open(`https://newpool.io/${chain}`);
      //   return;
      // }
      window.open(`https://newpool.io/${chain}`);
      break;
  }
}
// 被内嵌使用
export function getTargetOrigin() {
  const embedUrl = localStorage.getItem('swapEmbedUrl');
  if (embedUrl) {
    const paUrl = JSON.parse(embedUrl);
    const targetOrigin = decodeURIComponent(paUrl.origin);
    return targetOrigin;
  }
  const paUrl = getUrlParams(window.location.href);
  localStorage.setItem('swapEmbedUrl', JSON.stringify(paUrl));
  const targetOrigin = decodeURIComponent(paUrl.origin);
  return targetOrigin;
}

export function urlhostName() {
  const hostname = window.location.hostname;
  if (hostname.indexOf('vip') >= 0) {
    return 'vip';
  }
  if (hostname.indexOf('io') >= 0) {
    return 'io';
  }
  return 'vip'
}
